﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace LK.Math
{
    public partial class BitsTest{
        public static void Compare() {
            Log("Compare Test Start");
            Random r = new Random();
            ulong[] arr1 = new ulong[4];
            ulong[] arr2 = new ulong[4];
            ulong[] arr3 = new ulong[2];
            ulong[] arr4 = new ulong[0];
            for (int i = 0; i < 10000000; ++i) {
                int blen = r.Next(0, 129);
                int idx1 = r.Next(0,  arr1.Length * 64 - blen);
                int idx2 = r.Next(0, arr2.Length * 64 - blen);
                int idx3 = r.Next(0, arr3.Length * 64 - blen);
                //等长内容比较
                int cmp12 = Bits.Compare(arr1, idx1, arr2, idx2, blen);
                int cmp21 = Bits.Compare(arr2, idx2, arr1, idx1, blen);
                int cmp23 = Bits.Compare(arr2, idx2, arr3, idx3, blen);
                int cmp32 = Bits.Compare(arr3, idx3, arr2, idx2, blen);
                int cmp13 = Bits.Compare(arr1, idx1, arr3, idx3, blen);
                int cmp31 = Bits.Compare(arr3, idx3, arr1, idx1, blen);

                if (cmp12 != -cmp21 || cmp23 != -cmp32 || cmp13 != -cmp31)
                {
                    Log("Compare Error ");
                    System.Threading.Thread.Sleep(10000);
                }

                //高位对齐比较
                int hidx1 = r.Next(0, arr1.Length+1);
                int hidx2 = r.Next(0, arr2.Length+1);
                int hidx3 = r.Next(0, arr3.Length+1);
                int hcmp12 = Bits.HighAlignCompare(arr1,hidx1, arr2,hidx2);
                int hcmp21 = Bits.HighAlignCompare(arr2,hidx2, arr1,hidx1);
                int hcmp23 = Bits.HighAlignCompare(arr2,hidx2, arr3,hidx3);
                int hcmp32 = Bits.HighAlignCompare(arr3,hidx3, arr2,hidx2);
                int hcmp13 = Bits.HighAlignCompare(arr1, hidx1, arr3, hidx3);
                int hcmp31 = Bits.HighAlignCompare(arr3, hidx3, arr1, hidx1);
                int hcmp14 = Bits.HighAlignCompare(arr1, hidx1, arr4, 0);
                int hcmp24 = Bits.HighAlignCompare(arr2, hidx2, arr4, 0);
                int hcmp34 = Bits.HighAlignCompare(arr3, hidx3, arr4, 0);
                int hcmp41 = Bits.HighAlignCompare(arr4, 0, arr1, hidx1);
                int hcmp42 = Bits.HighAlignCompare(arr4, 0, arr2, hidx2);
                int hcmp43 = Bits.HighAlignCompare(arr4, 0, arr3, hidx3);
                if (hcmp12 != -hcmp21 || hcmp23 != -hcmp32 || hcmp13 != -hcmp31|| hcmp14 != -hcmp41 || hcmp43 != -hcmp34 || hcmp24 != -hcmp42)
                {
                    Log("HighAlignCompare Error ");
                    System.Threading.Thread.Sleep(10000);
                }

                //差值偏移比较
                int mov = r.Next(-129, 129);
                int dblen1 = r.Next(0, arr1.Length * 64+1);
                int dblen2 = r.Next(0, arr2.Length * 64+1);
                int didx1 = r.Next(0, arr1.Length * 64 - dblen1);
                int didx2 = r.Next(0, arr2.Length * 64 - dblen2);

                int dcmp12 = Bits.HighAlignDifferenceBitIndex(arr1, didx1, dblen1, arr2, didx2, dblen2, mov);
                int dcmp21 = Bits.HighAlignDifferenceBitIndex(arr2, didx2, dblen2, arr1, didx1, dblen1, -mov);
                if (dcmp12 != -dcmp21) {
                    Log("HighAlignDifferenceBitIndex Error ");
                    System.Threading.Thread.Sleep(10000);
                }

                ulong val = ((ulong)r.Next() << 40) ^ ((ulong)r.Next() << 20) ^ ((ulong)r.Next());
                arr1[r.Next(0, arr1.Length)] = val;
                val = ((ulong)r.Next() << 40) ^ ((ulong)r.Next() << 20) ^ ((ulong)r.Next());
                arr2[r.Next(0, arr2.Length)] = val;
                val = ((ulong)r.Next() << 40) ^ ((ulong)r.Next() << 20) ^ ((ulong)r.Next());
                arr3[r.Next(0, arr3.Length)] = val;


            }
            Log("Compare Test Done");

        }
        public static void Difference() {
            Random r = new Random();
            ulong[] t1 = new ulong[1];
            ulong[] t2 = new ulong[1];
            t1[0] = (ulong)r.Next() << 33;
            t2[0] = (ulong)r.Next() << 33;
            Bits b1 = Bits.CreateFromArray(t1);
            Bits b2 = Bits.CreateFromArray(t2);
            Console.WriteLine(b1);
            Console.WriteLine(b2);
            Console.WriteLine(0);
            Console.WriteLine(Bits.HighAlignDifferenceBitIndex(t1, 0, 64, t2, 0, 64, 0));
        }
    }
}
